import { Link } from '@brillout/docpress'
import { PropGlobalContext as Prop, ConfigSpec } from '../../components'

<ConfigSpec
  env="client, server"
  global={null}
/>

The `globalContext` object is used for storing global information (i.e. information shared by multiple pages).

It has <Link href="#built-in">built-in properties</Link> set by Vike, and you can define <Link href="#custom">custom properties</Link>.

For example, you can use `globalContext` to save the list of URLs for a navigation menu.

Each environment has a single, unique `globalContext` object created when it starts — see <Link href="#lifecycle" />. An environment can be either a server-side process (Node.js, Bun, Deno, or a worker) or a browser session.

If you store information (e.g. `globalContext.someData = 42`) then it's available anywhere in your app until the process is terminated. You can access `globalContext` anywhere by using <Link href="/getGlobalContext" noBreadcrumb /> and <Link href="/pageContext#globalContext">`pageContext.globalContext`</Link>. You can define `globalContext` properties on the server-side while using <Link href="/passToClient">`+passToClient`</Link> for accessing them on the client-side.

See also: <Link href="/pageContext" />.

> It only provides information at runtime. To get information at build-time, see <Link href="/getVikeConfig" /> instead.


## Built-in

While `globalContext` has some built-in properties, it's mostly used to store <Link href="#custom">custom properties</Link>.

> The `globalContext` object also contains many internals (they are prefixed with `_`, e.g. `globalContext._viteDevServer`). You should use them only if strictly needed and, if you do, then let us know so that we can add official support for your use case (otherwise you'll expose yourself to breaking changes upon any version update).

<Prop name="pages" />

Environment: server, client  

Eagerly loaded runtime <Link href="/config">configurations</Link> of all pages.

> Most configurations of a page aren't eagerly loaded: they're only loaded when rendering that page and, consequently, aren't available to other pages. Only a few configurations are eagerly loaded — the notable ones being <Link href="/route">the page's route</Link> and <Link href="/prefetchStaticAssets">the page's prefetch setting</Link>.

> Some page configurations aren't available at runtime; they are only available at config-time.

> See also: [`globalContext.config`](#config)

<Prop name="config" />

Environment: server, client  

The app's global runtime <Link href="/config">configuration</Link> (such as <Link href="/base-url">the base URL setting</Link>).

> Most global configurations aren't available at runtime; they are only available at config-time.

> See also:
> - <Link href="/pageContext#config">`pageContext.config`</Link>
> - [`globalContext.pages`](#pages)
> - <Link href="/getVikeConfig" />

<Prop name="prerenderContext" />

Environment: config (build-time)  

If you use <Link href="/pre-rendering">pre-rendering</Link>, you can access:
 - `globalContext.prerenderContext.pageContexts` — the list of all pre-rendered URLs.
 - `globalContext.prerenderContext.output` — the list of all written files.

See also: <Link href="/getVikeConfig" />

<Prop name="isClientSide" />

Environment: server, client  

Same as <Link href="/pageContext#isClientSide">`pageContext.isClientSide`</Link>.

It can also be used to narrow down the `GlobalContext` type to either `GlobalContextClient` or `GlobalContextServer`, see <Link href="#narrowing-down" />.

<Prop name="isGlobalContext" />

Environment: server, client  

Like <Link href="/pageContext#isPageContext">`pageContext.isPageContext`</Link>.

<Prop name="assetsManifest" />

Environment: server  

The <Link href="/preloading#assets-manifest">assets manifest</Link>.

<Prop name="viteConfig" />

Environment: server  

The entire Vite's config, only available at development and during <Link href="/pre-rendering">pre-rendering</Link>.

<Prop name="viteConfigRuntime" />

Environment: server  

A tiny subset of Vite's config that is also available in production.

<Prop name="baseAssets" />

Environment: server  

The <Link href="/base-url#baseassets">assets Base URL</Link>.

<Prop name="baseServer" />

Environment: server  

The <Link href="/base-url#baseserver">server Base URL</Link>.


## Custom

You can define custom `globalContext` properties.

```ts
globalContext.myCustomProp = someValue // Add or modify
```

Custom properties are typically initialized using one or several <Link href="/onCreateGlobalContext">`onCreateGlobalContext()` hooks</Link>.

You can also create and modify `globalContext` properties at any time and anywhere in your app — for example, in your UI components, using <Link href="/pageContext#globalContext">`pageContext.globalContext`</Link>.

> See the section <Link href="#extend">TypeScript > Extend</Link> for how to define the type of `globalContext.myCustomProp`.

See also: <Link href="/pageContext#custom" />.


## Lifecycle

> See also:
> - <Link href="/pageContext#lifecycle" />
> - <Link href="/hooks#lifecycle" />

The lifecycle of the `globalContext` object is completely different between the client- and server-side.

### Server-side

The `globalContext` is created when the server starts, and lives until the server process shuts down. For example, if your server process runs for 5 days, then the `globalContext` object lives for 5 days.

If your JavaScript server runs as a single process, then you have only one `globalContext` object for your entire server-side.

On edge environments, there are typically multiple server processes/workers, so you get multiple server-side `globalContext` objects — one per process/worker.

> In development, the `globalContext` object is re-initialized if you make a file change that triggers a full page reload (i.e. a change that isn't covered by HMR).

### Client-side

When a user starts visiting your website, a new `globalContext` object is created that lives until the user closes your website. If the user opens your website in multiple tabs, then there is one `globalContext` per tab.

For example, if 3 users are simultaneously visiting your website — two users with 1 tab and one user with 3 tabs — then there are 5 (`1 + 1 + 3 = 5`) client-side `globalContext` objects.

### Pre-rendering

Upon <Link href="/pre-rendering">pre-rendering</Link>, there is exactly one `globalContext` object that lives from the beginning until the end of the pre-rendering process.


## TypeScript

### Basics

```ts ts-only
import type {
  // For code loaded in client and server
  GlobalContext,
  // For code loaded in client only
  GlobalContextClient,
  // For code loaded in server only
  GlobalContextServer
} from 'vike/types'
```

### Narrowing down

You can use `globalContext.isClientSide` and `globalContext.isGlobalContext` to narrow down TypeScript unions, see <Link href="/pageContext#narrowing-down" />.

### Extend

To extend `GlobalContext`/`GlobalContextServer`/`GlobalContextClient`, use the global interface `Vike.GlobalContext`:

```ts ts-only
declare global {
  namespace Vike {
    interface GlobalContext {
      // Type of globalContext.user
      user?: {
        name: string
        id: string
        isAdmin: boolean
      }
    }
  }
}

// If you define Vike.GlobalContext in a .d.ts file then
// make sure there is at least one export/import statement.
// Tell TypeScript this file isn't an ambient module:
export {}
```

To define properties only for the server-/client-side, use the interfaces `Vike.GlobalContextServer` and `Vike.GlobalContextClient` instead.


## See also

- <Link href="/pageContext" />
- <Link href="/getGlobalContext" />
- <Link href="/getVikeConfig">API > `getVikeConfig()`</Link>
- <Link href="/onCreateGlobalContext" />
- <Link href="/passToClient" />
